interface I {
    events: Map<string, Function[]>
    once: (event: string, cb: Function) => void
    on: (event: string, cb: Function) => void
    emit: (event: string, ...args: any[]) => void
    off: (event: string, cb: Function) => void
}
class Bundle implements I {
    events: Map<string, Function[]>
    constructor() {
        this.events = new Map<string, Function[]>
    }
    once(event: string, cb: Function) {
        // 调用一次后就清除
        const fn = (...args:any[]) => {
            cb(...args)
            this.off(event, fn)
        }
        this.on(event, fn)
    }
    on(event: string, cb: Function) {
        if (!this.events.has(event)) {
            this.events.set(event, [cb])
        } else {
            this.events.get(event)?.push(cb)
        }
    }
    emit(event: string, ...args: any[]) {
        let eventArr: Function[] = this.events.get(event) || []
        for (const fn of eventArr) {
            fn(...args)
        }

    }
    off(event: string, cb: Function) {
        let eventArr = this.events.get(event) || []
        if (eventArr.indexOf(cb) !== -1) {
            eventArr?.splice(eventArr.indexOf(cb), 1)
        }
    }
}

const bus = new Bundle()
let fn = (...args: any[]) => {
    console.log('msg', ...args)
}
let fun = (...args: any[]) => {
    console.log('once:', ...args)
}
bus.on('msg1', fn)
bus.on('msg1', (...args: any[]) => { console.log(...args, 'sb') })
bus.emit('msg1', 1, 1, 1, 1)
bus.off('msg1', fn)
bus.emit('msg1', 1, 1, 1, 1)

console.log('---------------')

bus.once('once', fun)
bus.emit('once', 'ooo')
bus.emit('once', 'ooo')


// bus.on('msg2', fn)
// bus.emit('msg2', 2, 2, 2, 2)

// bus.on('msg3', fn)
// bus.emit('msg3', 3, 3, 3, 3)

